package org.peterf.foxish.net;

import java.io.BufferedReader;
import java.io.InputStreamReader;
import java.net.HttpURLConnection;
import java.net.URL;

import android.os.Handler;
import android.os.Message;

public class TextDownloader extends Thread {

    public static enum DataMode {
        AS_WHOLE, PER_LINE
    }

    public static final int NOTIFY_NEW_DATA = 0x2;

    public static final int RESULT_FAIL = 0x1;

    public static final int RESULT_OK = 0x3;

    HttpURLConnection connection;

    private String address;

    private Handler handler;

    private DataMode mode;

    private BufferedReader reader;

    public TextDownloader(String address, DataMode mode, Handler handler) {
        this.address = address;
        this.mode = mode;
        this.handler = handler;
    }

    public void cancel() {
        connection.disconnect();
        // TODO Above is wrong.
    }

    @Override
    public void run() {
        try {
            URL url = new URL(address);
            connection = (HttpURLConnection) url.openConnection();
            connection.connect();
            InputStreamReader r = new InputStreamReader(
                    connection.getInputStream());
            reader = new BufferedReader(r);
            if (mode == DataMode.AS_WHOLE) {
                transferAsWhole(reader);
            } else if (mode == DataMode.PER_LINE) {
                transferPerLine(reader);
            }
            reader.close();
            handler.sendEmptyMessage(RESULT_OK);
        } catch (Exception e) {
            handler.sendEmptyMessage(RESULT_FAIL);
        }
    }

    private void transferAsWhole(BufferedReader reader) throws Exception {
        final int BUFFER_SIZE = 4096;
        char[] buffer = new char[BUFFER_SIZE];
        StringBuilder builder = new StringBuilder(BUFFER_SIZE >> 2);
        while (true) {
            int count = reader.read(buffer, 0, BUFFER_SIZE);
            if (count == -1) {
                break;
            }
            builder.append(buffer, 0, count);
        }
        Message msg = Message.obtain(handler, NOTIFY_NEW_DATA);
        msg.obj = builder.toString();
        handler.sendMessage(msg);
    }

    private void transferPerLine(BufferedReader reader) throws Exception {
        while (true) {
            String line = reader.readLine();
            if (line == null) {
                break;
            }
            Message msg = Message.obtain(handler, NOTIFY_NEW_DATA);
            msg.obj = line;
            handler.sendMessage(msg);
        }
    }

}
